<template>
  <div class="work-order-container">
    <el-page-header content="运维工单管理" style="margin-bottom: 20px;"></el-page-header>

    <!-- 筛选和操作区 -->
    <el-card shadow="hover" class="filter-card">
      <div class="filter-container">
        <el-select
            v-model="statusFilter"
            placeholder="筛选工单状态"
            clearable
            style="width: 200px; margin-right: 20px;"
            @change="fetchWorkOrderList"
        >
          <el-option label="待办" value="1"></el-option>
          <el-option label="处理中" value="2"></el-option>
          <el-option label="已处理" value="3"></el-option>
          <el-option label="处理失败" value="4"></el-option>
        </el-select>
      </div>
    </el-card>

    <!-- 工单列表 -->
    <el-card shadow="hover" class="stat-card" style="margin-top: 20px;">
      <el-table
          :data="workOrderList"
          border
          style="width: 100%;"
          v-loading="tableLoading"
      >
        <el-table-column prop="repairId" label="工单ID" width="140"></el-table-column>
        <el-table-column prop="faultId" label="关联故障ID" width="120"></el-table-column>
        <el-table-column prop="deviceId" label="设备ID" width="120"></el-table-column>
        <el-table-column prop="status" label="状态" width="120">
          <template slot-scope="scope">
            <el-tag :type="getStatusTag(scope.row.repairResult).type">
              {{ getStatusTag(scope.row.repairResult).text }}
            </el-tag>
          </template>
        </el-table-column>
        <el-table-column prop="priority" label="优先级" width="120">
          <template slot-scope="scope">
            <el-tag :type="getPriorityTag(scope.row.priority).type">
              {{ getPriorityTag(scope.row.priority).text }}
            </el-tag>
          </template>
        </el-table-column>

        <!-- 维修照片列 -->
        <el-table-column label="维修照片" width="140">
          <template slot-scope="scope">
            <el-image
                :src="scope.row.repairImages"
                style="width: 80px; height: 80px; border-radius: 4px;"
                fit="cover"
                preview-src-list="[scope.row.repairImages]"
                v-if="scope.row.repairImages"
                class="photo-preview"
            ></el-image>
            <div v-else class="no-photo">无照片</div>
          </template>
        </el-table-column>

        <el-table-column prop="createTime" label="创建时间" width="180"></el-table-column>
        <el-table-column label="操作" width="260">
          <template slot-scope="scope">
            <el-button type="text" size="mini" @click="openDetailDialog(scope.row.repairId)">
              查看详情
            </el-button>
            <el-tooltip
                :content="getProcessBtnTooltip(scope.row)"
                placement="top"
                :disabled="canProcess(scope.row)"
            >
              <el-button
                  type="text"
                  size="mini"
                  @click="handleProcessWorkOrder(scope.row)"
                  :disabled="!canProcess(scope.row)"
                  :class="{ 'disabled-btn': !canProcess(scope.row) }"
                  @click.native="handleProcessButtonClick(scope.row)"
              >
                {{ getProcessBtnText(scope.row.repairResult) }}
              </el-button>
            </el-tooltip>

            <!-- 上传照片按钮 -->
            <el-button
                type="text"
                size="mini"
                @click="handleUploadPhoto(scope.row)"
                :disabled="!canUpload(scope.row.repairResult)"
                class="upload-btn"
            >
              <i class="el-icon-upload2"></i> 上传照片
            </el-button>
          </template>
        </el-table-column>
      </el-table>

      <!-- 分页 -->
      <el-pagination
          @size-change="handleSizeChange"
          @current-change="handleCurrentChange"
          :current-page="currentPage"
          :page-sizes="[10, 20, 30]"
          :page-size="pageSize"
          layout="total, sizes, prev, pager, next, jumper"
          :total="total"
          style="margin-top: 15px; text-align: right;"
      ></el-pagination>
    </el-card>

    <!-- 详情弹窗 -->
    <el-dialog
        title="工单详情"
        :visible.sync="detailDialogVisible"
        width="700px"
    >
      <div v-if="currentWorkOrder" class="detail-content">
        <el-descriptions column="1" border>
          <el-descriptions-item label="工单ID">{{ currentWorkOrder.repairId }}</el-descriptions-item>
          <el-descriptions-item label="关联故障ID">{{ currentWorkOrder.faultId }}</el-descriptions-item>
          <el-descriptions-item label="设备ID">{{ currentWorkOrder.deviceId }}</el-descriptions-item>
          <el-descriptions-item label="状态">
            <el-tag :type="getStatusTag(currentWorkOrder.repairResult).type">
              {{ getStatusTag(currentWorkOrder.repairResult).text }}
            </el-tag>
          </el-descriptions-item>
          <el-descriptions-item label="优先级">
            <el-tag :type="getPriorityTag(currentWorkOrder.priority).type">
              {{ getPriorityTag(currentWorkOrder.priority).text }}
            </el-tag>
          </el-descriptions-item>
          <el-descriptions-item label="维修照片" v-if="currentWorkOrder.repairImages">
            <el-image
                :src="currentWorkOrder.repairImages"
                style="width: 300px; height: 200px; border-radius: 4px;"
                fit="contain"
            ></el-image>
          </el-descriptions-item>
          <el-descriptions-item label="创建时间">{{ currentWorkOrder.createTime }}</el-descriptions-item>
          <el-descriptions-item label="开始处理时间">{{ currentWorkOrder.startTime || '未开始' }}</el-descriptions-item>
          <el-descriptions-item label="处理结束时间">{{ currentWorkOrder.endTime || '未结束' }}</el-descriptions-item>
          <el-descriptions-item label="维修备注">{{ currentWorkOrder.repairNotes || '无' }}</el-descriptions-item>
        </el-descriptions>
        <el-button
            type="text"
            @click="openStatusHistoryDialog(currentWorkOrder.repairId)"
            style="margin-top: 10px;"
        >
          查看状态变更历史
        </el-button>
      </div>
    </el-dialog>

    <!-- 处理工单弹窗 -->
    <el-dialog
        :title="processDialogTitle"
        :visible.sync="processDialogVisible"
        width="500px"
    >
      <el-form
          :model="processForm"
          :rules="processRules"
          ref="processFormRef"
          label-width="120px"
      >
        <!-- 重新分配时显示处理人ID输入框 -->
        <el-form-item label="处理人ID" prop="processorId" v-if="showProcessorInput">
          <el-input
              v-model="processForm.processorId"
              placeholder="请输入处理人ID"
          ></el-input>
        </el-form-item>
        <el-form-item label="维修备注" prop="repairNotes" v-if="showRepairNotes">
          <el-input
              v-model="processForm.repairNotes"
              type="textarea"
              rows="4"
          ></el-input>
        </el-form-item>
        <el-form-item label="失败原因" prop="failureReason" v-if="showFailureReason">
          <el-input
              v-model="processForm.failureReason"
              type="textarea"
              rows="4"
          ></el-input>
        </el-form-item>
        <el-form-item label="维修图片" prop="repairImages" v-if="showRepairImages">
          <el-upload
              action=""
              :auto-upload="false"
              :on-change="handleImageChange"
              list-type="picture"
          >
            <el-button size="small" type="primary">点击上传</el-button>
          </el-upload>
        </el-form-item>
      </el-form>
      <div slot="footer">
        <el-button @click="processDialogVisible = false">取消</el-button>
        <el-button type="primary" @click="submitProcessForm">确认提交</el-button>
      </div>
    </el-dialog>

    <!-- 优化后的上传照片窗口 -->
    <el-dialog
        title="上传维修照片"
        :visible.sync="uploadDialogVisible"
        width="500px"
        :close-on-click-modal="false"
        class="upload-dialog"
    >
      <!-- 上传区域 -->
      <div class="upload-container">
        <!-- 拖放上传区域 -->
        <div
            class="upload-area"
            @click="triggerFileSelect"
            @dragover.prevent
            @drop.prevent="handleFileDrop"
        >
          <i class="el-icon-picture-outline upload-icon"></i>
          <p class="upload-text">点击或拖拽图片到此处上传</p>
          <p class="upload-tip">支持 JPG、PNG 格式，单张不超过 5MB</p>
          <input
              type="file"
              ref="fileInput"
              accept="image/jpeg,image/png"
              @change="handleFileSelect"
              class="file-input"
          >
        </div>

        <!-- 已选择图片预览 -->
        <div v-if="selectedImageUrl" class="image-preview-container">
          <div class="preview-title">预览：</div>
          <el-image
              :src="selectedImageUrl"
              class="preview-image"
              fit="contain"
          ></el-image>
        </div>
      </div>

      <div slot="footer" class="dialog-footer">
        <el-button @click="cancelUpload">取消</el-button>
        <el-button
            type="primary"
            @click="submitUpload"
            :disabled="!selectedImageUrl"
            class="confirm-btn"
        >
          确认上传
        </el-button>
      </div>
    </el-dialog>
  </div>
</template>

<script>
import { Message } from "element-ui";
import { workorder } from "@/api/workorder";

export default {
  name: "WorkOrderManage",
  data() {
    return {
      // 列表数据
      workOrderList: [],
      total: 0,
      currentPage: 1,
      pageSize: 10,
      tableLoading: false,
      statusFilter: "",

      // 弹窗控制
      detailDialogVisible: false,
      processDialogVisible: false,
      statusHistoryDialogVisible: false,
      uploadDialogVisible: false, // 上传照片弹窗控制

      // 当前操作的工单数据
      currentWorkOrder: null,
      currentProcessType: "", // 'reassign' 重新分配
      statusHistoryList: [],
      currentUploadRow: null, // 当前上传照片的工单
      selectedImageUrl: "", // 选中的图片预览地址
      selectedFile: null, // 选中的文件对象

      // 处理工单表单
      processForm: {
        processorId: "",
        repairNotes: "",
        failureReason: "",
        repairImages: ""
      },
      processRules: {
        processorId: [{ required: true, message: "请输入处理人ID", trigger: "blur" }],
        repairNotes: [{ required: true, message: "请输入维修备注", trigger: "blur" }],
        failureReason: [{ required: true, message: "请输入失败原因", trigger: "blur" }]
      }
    };
  },
  computed: {
    processDialogTitle() {
      const titles = {
        start: "开始处理工单",
        complete: "完成工单处理",
        fail: "标记处理失败",
        reassign: "重新分配工单"
      };
      return titles[this.currentProcessType] || "处理工单";
    },
    // 仅重新分配时显示处理人输入框
    showProcessorInput() {
      return this.currentProcessType === "reassign";
    },
    showRepairNotes() {
      return this.currentProcessType === "complete";
    },
    showFailureReason() {
      return this.currentProcessType === "fail";
    },
    showRepairImages() {
      return this.currentProcessType === "complete";
    }
  },
  mounted() {
    this.fetchWorkOrderList();
  },
  methods: {
    // 获取工单列表
    fetchWorkOrderList() {
      this.tableLoading = true;
      const statusNum = this.statusFilter ? Number(this.statusFilter) : undefined;
      const userId = localStorage.getItem('userId');
      workorder.list({
        status: statusNum || undefined,
        pageNum: this.currentPage,
        pageSize: this.pageSize,
        processorId: userId,
      })
          .then(res => {
            this.workOrderList = res.data.records.reverse();
            this.total = res.data.total;
          })
          .catch(err => {
            Message.error("获取工单列表失败：" + (err.message || err));
          })
          .finally(() => {
            this.tableLoading = false;
          });
    },

    // 分页处理
    handleSizeChange(val) {
      this.pageSize = val;
      this.currentPage = 1;
      this.fetchWorkOrderList();
    },
    handleCurrentChange(val) {
      this.currentPage = val;
      this.fetchWorkOrderList();
    },

    // 状态标签样式
    getStatusTag(status) {
      const statusMap = {
        1: { text: "待办", type: "warning" },
        2: { text: "处理中", type: "info" },
        3: { text: "已处理", type: "success" },
        4: { text: "处理失败", type: "danger" }
      };
      return statusMap[status] || { text: "未知", type: "default" };
    },

    // 优先级标签样式
    getPriorityTag(priority) {
      const priorityMap = {
        1: { text: "紧急", type: "danger" },
        2: { text: "普通", type: "primary" },
        3: { text: "低", type: "info" }
      };
      return priorityMap[priority] || { text: "未知", type: "default" };
    },

    // 处理按钮文本
    getProcessBtnText(status) {
      const btnTextMap = {
        1: "确认工单",    // 待办状态
        2: "完成处理",    // 处理中状态
        3: "完成处理",    // 已完成状态
        4: "重新分配"     // 处理失败状态
      };
      return btnTextMap[status] || "操作";
    },

    // 判断是否可处理
    canProcess(row) {
      const status = row.repairResult;
      // 待办(1)、处理失败(4)状态始终可操作
      if ([1, 4].includes(status)) {
        return true;
      }
      // 处理中状态(2)：必须已上传照片才能操作
      if (status === 2) {
        return !!row.repairImages; // 有照片返回true，无照片返回false
      }
      // 已完成状态(3)不可操作
      return false;
    },

    // 处理按钮提示文本
    getProcessBtnTooltip(row) {
      if (row.repairResult === 2 && !row.repairImages) {
        return "请先上传维修照片才能完成处理";
      }
      return "";
    },

    // 处理按钮点击事件（处理禁用状态下的点击反馈）
    handleProcessButtonClick(row) {
      if (row.repairResult === 2 && !row.repairImages) {
        Message.warning("请先上传维修照片才能完成处理");
      }
    },

    // 判断是否可上传照片
    canUpload(status) {
      // 仅“处理中”状态可上传
      if (status === undefined || status === null) {
        console.warn('[canUpload] 无效的工单状态：', status);
        return false;
      }
      return Number(status) === 2;
    },

    // 打开详情弹窗
    openDetailDialog(repairId) {
      workorder.detail({workOrderId: repairId})
          .then(res => {
            this.currentWorkOrder = res.data;
            this.detailDialogVisible = true;
          })
          .catch(err => {
            Message.error("获取工单详情失败：" + (err.message || err));
          });
    },

    // 打开状态历史弹窗
    openStatusHistoryDialog(repairId) {
      workorder.history({workOrderId: repairId})
          .then(res => {
            this.statusHistoryList = res.data;
            this.statusHistoryDialogVisible = true;
          })
          .catch(err => {
            Message.error("获取状态历史失败：" + (err.message || err));
          });
    },

    // 处理工单入口
    handleProcessWorkOrder(row) {
      this.currentWorkOrder = {...row};
      this.processForm = {
        processorId: localStorage.getItem('userId'), // 默认填充当前用户ID
        repairNotes: "",
        failureReason: "",
        repairImages: ""
      };

      switch (row.repairResult) {
        case 1: // 待办状态 - 确认工单（无弹窗直接处理）
          this.confirmWorkOrder(row);
          break;

        case 2: // 处理中状态 - 完成处理
          this.$confirm("请选择处理方式", "提示", {
            confirmButtonText: "完成处理",
            cancelButtonText: "标记失败",
            type: "info"
          })
              .then(() => {
                this.currentProcessType = "complete";
                this.processDialogVisible = true;
              })
              .catch(() => {
                this.currentProcessType = "fail";
                this.processDialogVisible = true;
              });
          break;

        case 4: // 处理失败状态 - 重新分配
          this.currentProcessType = "reassign";
          this.processDialogVisible = true;
          break;
      }
    },

    // 确认工单（无弹窗直接处理）
    confirmWorkOrder(row) {
      // 显示加载状态
      this.tableLoading = true;

      // 准备更新数据：状态改为处理中(2)，设置处理人ID和开始时间
      const updateData = {
        repairId: row.repairId,
        anomalyId: row.faultId ? Number(row.faultId) : null,
        deviceId: row.deviceId,
        processorId: localStorage.getItem('userId'),
        repairResult: 2,
      };

      console.log('[confirmWorkOrder] 确认工单，更新数据：', updateData);

      workorder.update(updateData)
          .then(response => {
            console.log('[confirmWorkOrder] 确认工单成功：', response);
            Message.success("工单已确认，状态变为处理中");
            this.fetchWorkOrderList(); // 刷新列表
          })
          .catch(err => {
            console.error('[confirmWorkOrder] 确认工单失败：', err);
            Message.error("确认工单失败：" + (err.message || err));
          })
          .finally(() => {
            this.tableLoading = false; // 关闭加载状态
          });
    },

    // 提交处理表单
    submitProcessForm() {
      this.$refs.processFormRef.validate(valid => {
        if (!valid) return;

        const repairId = this.currentWorkOrder.repairId;
        let apiMethod, params;

        switch (this.currentProcessType) {
          case "reassign": // 重新分配
            apiMethod = workorder.updateProcessor;
            params = {
              repairId: repairId,
              processorId: this.processForm.processorId
            };
            break;
          case "complete":
            apiMethod = workorder.complete;
            params = {
              workOrderId: repairId,
              notes: this.processForm.repairNotes,
              images: this.processForm.repairImages,
              endTime: this.formatDateForBackend(new Date())
            };
            break;
          case "fail":
            apiMethod = workorder.fail;
            params = {
              workOrderId: repairId,
              failureReason: this.processForm.failureReason,
              endTime: this.formatDateForBackend(new Date())
            };
            break;
          default:
            return;
        }

        apiMethod(params)
            .then(() => {
              Message.success({
                'reassign': '工单已重新分配',
                'complete': '工单已完成处理',
                'fail': '工单已标记为处理失败'
              }[this.currentProcessType]);
              this.processDialogVisible = false;
              this.fetchWorkOrderList();
            })
            .catch(err => {
              Message.error("处理工单失败：" + (err.message || err));
            });
      });
    },

    // 格式化日期为后端可识别的格式
    formatDateForBackend(date) {
      const year = date.getFullYear();
      const month = String(date.getMonth() + 1).padStart(2, '0');
      const day = String(date.getDate()).padStart(2, '0');
      const hours = String(date.getHours()).padStart(2, '0');
      const minutes = String(date.getMinutes()).padStart(2, '0');
      const seconds = String(date.getSeconds()).padStart(2, '0');

      return `${year}-${month}-${day} ${hours}:${minutes}:${seconds}`;
    },

    // 图片上传处理（处理工单弹窗内）
    handleImageChange(file) {
      this.processForm.repairImages = URL.createObjectURL(file.raw);
    },

    // 打开上传照片窗口
    handleUploadPhoto(row) {
      this.currentUploadRow = row;
      this.selectedImageUrl = ""; // 重置选中图片
      this.selectedFile = null;
      this.uploadDialogVisible = true;
    },

    // 触发文件选择
    triggerFileSelect() {
      this.$refs.fileInput.click();
    },

    // 处理文件选择
    handleFileSelect(e) {
      const file = e.target.files[0];
      if (file) {
        this.validateFile(file);
      }
    },

    // 处理拖放文件
    handleFileDrop(e) {
      const file = e.dataTransfer.files[0];
      if (file) {
        this.validateFile(file);
      }
    },

    // 验证文件格式和大小
    validateFile(file) {
      // 验证格式
      const validTypes = ['image/jpeg', 'image/png'];
      if (!validTypes.includes(file.type)) {
        Message.error("请上传 JPG 或 PNG 格式的图片");
        return;
      }

      // 验证大小（5MB）
      if (file.size > 5 * 1024 * 1024) {
        Message.error("图片大小不能超过 5MB");
        return;
      }

      // 预览图片
      this.selectedFile = file;
      const reader = new FileReader();
      reader.onload = (e) => {
        this.selectedImageUrl = e.target.result;
      };
      reader.readAsDataURL(file);
    },

    // 提交上传
    submitUpload() {
      console.log('[submitUpload] 开始执行上传操作');
      if (!this.selectedFile) {
        console.warn('[submitUpload] 未选中任何文件，终止上传');
        return;
      }

      const formData = new FormData();
      formData.append('file', this.selectedFile);

      console.log('[submitUpload] 准备发送上传请求');

      workorder.upload(formData)
          .then(response => {
            console.log('[submitUpload] 上传请求成功返回：', response);

            if (response.code === 200) {
              const imageUrl = response.data;
              console.log('[submitUpload] 上传成功，图片URL：', imageUrl);
              this.updateWorkOrderImage(this.currentUploadRow, imageUrl);
            } else {
              console.error('[submitUpload] 上传失败：', response.msg || '未知错误');
              Message.error("上传失败：" + (response.msg || "未知错误"));
            }
          })
          .catch(err => {
            console.error('[submitUpload] 上传异常：', err);
            Message.error("上传失败：" + (err.message || "网络错误"));
          });
    },

    // 更新工单照片地址
    updateWorkOrderImage(workOrder, imageUrl) {
      const formattedDate = this.formatDateForBackend(new Date());

      const updateData = {
        repairId: workOrder.repairId,
        anomalyId: workOrder.faultId ? Number(workOrder.faultId) : null,
        deviceId: workOrder.deviceId,
        repairResult: workOrder.repairResult,
        processorId: localStorage.getItem('userId'),
        repairImages: imageUrl,
        repairTime: formattedDate
      };

      console.log('[updateWorkOrderImage] 更新照片：', updateData);

      workorder.update(updateData)
          .then(response => {
            console.log('[updateWorkOrderImage] 更新成功：', response);
            if (response.code === 200) {
              Message.success("照片上传成功");
              this.uploadDialogVisible = false;
              this.fetchWorkOrderList();
            } else {
              Message.error("更新照片失败：" + (response.msg || "未知错误"));
            }
          })
          .catch(err => {
            console.error('[updateWorkOrderImage] 更新失败：', err);
            Message.error("更新照片失败：" + (err.message || err));
          });
    },

    // 取消上传
    cancelUpload() {
      this.uploadDialogVisible = false;
      this.selectedImageUrl = "";
      this.selectedFile = null;
    },
  }
};
</script>

<style scoped>
.work-order-container {
  padding: 20px;
  background-color: #f5f7fa;
}

.filter-card {
  padding: 15px;
  margin-bottom: 20px;
}

.filter-container {
  display: flex;
  align-items: center;
  flex-wrap: wrap;
  gap: 10px;
}

.detail-content {
  margin-top: 10px;
}

/* 照片列样式 */
.photo-preview {
  cursor: pointer;
  transition: transform 0.2s;
}

.photo-preview:hover {
  transform: scale(1.05);
}

.no-photo {
  width: 80px;
  height: 80px;
  line-height: 80px;
  text-align: center;
  background-color: #f5f5f5;
  border-radius: 4px;
  color: #999;
  font-size: 12px;
}

/* 按钮样式 */
.upload-btn {
  color: #409eff !important;
}

.upload-btn .el-icon-upload2 {
  margin-right: 3px;
}

.disabled-btn {
  color: #c0c4cc !important;
  cursor: not-allowed !important;
}

/* 上传弹窗样式 */
.upload-dialog .el-dialog__header {
  padding: 18px 20px;
  border-bottom: 1px solid #f0f0f0;
}

.upload-area {
  width: 100%;
  height: 180px;
  border: 2px dashed #dcdfe6;
  border-radius: 8px;
  display: flex;
  flex-direction: column;
  align-items: center;
  justify-content: center;
  cursor: pointer;
  transition: all 0.3s;
  background-color: #fafafa;
}

.upload-area:hover {
  border-color: #409eff;
  background-color: #f0f7ff;
}

.upload-icon {
  font-size: 36px;
  color: #409eff;
  margin-bottom: 15px;
}

.image-preview-container {
  margin-top: 20px;
  padding-top: 15px;
  border-top: 1px solid #f0f0f0;
}

.preview-image {
  width: 100%;
  max-height: 200px;
  border-radius: 4px;
}

.dialog-footer {
  padding: 10px 20px 15px;
  background-color: #f5f7fa;
  border-top: 1px solid #f0f0f0;
}
</style>